/*
                    MouseContextMenu Class Implementation
*/
#include "MouseContextMenu.h"

MouseContextMenu::MouseContextMenu()
{
    strName = "";
    strMenuTargetData = "";

    iFontSize = 12;

    Position = Point(0, 0);

    Background = NULL;
}

MouseContextMenu::~MouseContextMenu()
{
    for (int i = 0; i < MenuItems.size(); i++)
    {
        delete MenuItems.at(i);
    }

    MenuItems.clear();

    if (Background != NULL)
    {
        SDL_FreeSurface(Background);
    }
}

void MouseContextMenu::Initialise(const string& strNewName, const vector<string>& NewItems, const int& iNewFontSize, SDL_Color Colour, SDL_Color MouseoverColour,
                                const int& iVPadding, const int& iHPadding, const int& iSpacing, const string& strHeaderBG, const string& strFooterBG, const string& strBackBG)
{
    strName = strNewName;
    iFontSize = iNewFontSize;

    SDL_Surface *Header = OptimiseAlphaSurface(IMG_Load(strHeaderBG.c_str()));
    SDL_Surface *Footer = OptimiseAlphaSurface(IMG_Load(strFooterBG.c_str()));

    int iBGWidth = 0;
    int iBGHeight = iVPadding;
    int iHeaderHeight = 0;
    int iFooterHeight = 0;

    if (Header != NULL)
    {
        iBGWidth = Header->w;

        iHeaderHeight = Header->h;
    }

    if (Footer != NULL)
    {
        if (Footer->w > iBGWidth)
        {
            iBGWidth = Footer->w;
        }

        iFooterHeight = Footer->h;
    }

    int iCurrentHeight = 0;

    for (int i = 0; i < NewItems.size(); i++)
    {
        iCurrentHeight = (iVPadding + iHeaderHeight) + (i * (iSpacing + iFontSize));

        MenuItems.push_back(new ContextMenuItem);
        MenuItems.back()->lblNormal.Initialise(Point(iHPadding, iCurrentHeight), "Data//Fonts//gui.ttf", iFontSize, NewItems.at(i), Colour);
        MenuItems.back()->lblHover.Initialise(Point(iHPadding, iCurrentHeight), "Data//Fonts//gui.ttf", iFontSize, NewItems.at(i), MouseoverColour);
    }

    iBGHeight = iCurrentHeight + (iVPadding * 2) + iHeaderHeight + iFooterHeight;

    Background = OptimiseAlphaSurface(SDL_CreateRGBSurface(SDL_HWSURFACE | SDL_SRCALPHA, iBGWidth, iBGHeight, 32, RMASK, GMASK, BMASK, AMASK));

    SDL_FillRect(Background, NULL, SDL_MapRGBA(Background->format, 0, 0, 0, 150));

    SDL_Rect header, footer;
    header.w = iBGWidth;
    header.h = iHeaderHeight;
    header.x = 0;
    header.y = 0;

    footer.w = iBGWidth;
    footer.h = iFooterHeight;
    footer.x = 0;
    footer.y = iBGHeight - iFooterHeight;

    SDL_FillRect(Background, &header, SDL_MapRGBA(Background->format, 0, 0, 0, SDL_ALPHA_OPAQUE));
    SDL_FillRect(Background, &footer, SDL_MapRGBA(Background->format, 0, 0, 0, SDL_ALPHA_OPAQUE));

    if (Background != NULL)
    {
        SDL_Rect dest;

        if (Header != NULL)
        {
            dest.x = 0;
            dest.y = 0;
            SDL_BlitSurface(Header, NULL, Background, &dest);

            SDL_FreeSurface(Header);
        }

        if (Footer != NULL)
        {
            dest.y = iBGHeight - Footer->h;
            SDL_BlitSurface(Footer, NULL, Background, &dest);

            SDL_FreeSurface(Footer);
        }

        /*
        SDL_Surface *Back = OptimiseAlphaSurface(IMG_Load(strBackBG.c_str()));

        if (Back != NULL)
        {
            SDL_Rect fillrect;
            fillrect.w = Background->w;
            fillrect.h = Background->h - (iHeaderHeight + iFooterHeight);
            fillrect.x = 0;
            fillrect.y = iHeaderHeight;

            TileFillSurfaceFromSurface(fillrect, Background, Back);

            SDL_FreeSurface(Back);
        }
        */
    }
}

void MouseContextMenu::OpenMenu(const Point& OpenPosition, const string& strTargetData)
{
    Position = OpenPosition;
    strMenuTargetData = strTargetData;

    bVisible = true;
}

void MouseContextMenu::CloseMenu()
{
    bVisible = false;
    strMenuTargetData = "";

    for (int i = 0; i < MenuItems.size(); i++)
    {
        MenuItems.at(i)->bMouseOver = false;
    }
}

void MouseContextMenu::HandleMouseMotion(const int& iMouseXREL, const int& iMouseYREL)
{
    if (Background == NULL)
    {
        return;
    }

    int iMouseX, iMouseY;

    SDL_GetMouseState(&iMouseX, &iMouseY);

    if((iMouseX > Position.x) && (iMouseX < Position.x + Background->w) && (iMouseY > Position.y) && (iMouseY < Position.y + Background->h))
    {
        for (int i = 0; i < MenuItems.size(); i++)
        {
            if (MenuItems.at(i)->lblNormal.HandleMouseDown(iMouseX - (int)Position.x, iMouseY - (int)Position.y) == 1)
            {
                MenuItems.at(i)->bMouseOver = true;
            }
            else
            {
                MenuItems.at(i)->bMouseOver = false;
            }
        }
    }
}

string MouseContextMenu::HandleMouseUp(int iMouseX, int iMouseY)
{
    if (Background == NULL)
    {
        return "";
    }

    if((iMouseX > Position.x) && (iMouseX < Position.x + Background->w) && (iMouseY > Position.y) && (iMouseY < Position.y + Background->h))
    {
        for (int i = 0; i < MenuItems.size(); i++)
        {
            if (MenuItems.at(i)->lblNormal.HandleMouseDown(iMouseX - (int)Position.x, iMouseY - (int)Position.y) == 1)
            {
                return MenuItems.at(i)->lblNormal.getText();
            }
        }
    }

    return "";
}

void MouseContextMenu::BlitToSurface(SDL_Surface *surface)
{
    if (bVisible == true)
    {
        SDL_Rect dest;

        dest.x = (int)Position.x;
        dest.y = (int)Position.y;

        SDL_BlitSurface(Background, NULL, surface, &dest);

        for (int i = 0; i < MenuItems.size(); i++)
        {
            if (MenuItems.at(i)->bMouseOver == true)
            {
                MenuItems.at(i)->lblHover.BlitToFrame(surface, Position);
            }
            else
            {
                MenuItems.at(i)->lblNormal.BlitToFrame(surface, Position);
            }
        }
    }
}

void MouseContextMenu::setName(const string& strNewName)
{
    strName = strNewName;
}

string MouseContextMenu::getName()
{
    return strName;
}

void MouseContextMenu::setTargetData(const string& strNewTargetData)
{
    strMenuTargetData = strNewTargetData;
}

string MouseContextMenu::getTargetData()
{
    return strMenuTargetData;
}

void MouseContextMenu::setFontSize(const int& iNewFontSize)
{
    iFontSize = iNewFontSize;
}

int MouseContextMenu::getFontSize()
{
    return iFontSize;
}
